Imports System.Threading
'Imports System.Data.OleDb
'Imports System.Data.odbc

Public Enum NotifyCommand
    ChangeListBox
End Enum

Public Class ServerTimer
    Private MyServerTimer As Timer
    Private MyCheckInterval As Integer = 0
    Private MyTimeOutValue As Integer = 0
    Private MyServerCnn As New DBConnection

    Public Delegate Sub OnServerTimerEventDelegate(ByVal StatusMessage As String, ByVal ProcessMessage As String)
    Private MyOnServerTimerEventDelegate As OnServerTimerEventDelegate

    Dim autoEvents() As AutoResetEvent
    Dim manualEvent As ManualResetEvent

    Public Sub New(ByVal ServerTimerEventDelegate As OnServerTimerEventDelegate, ByVal iCheckInterval As Integer, ByVal iTimeOutValue As Integer)
        MyOnServerTimerEventDelegate = ServerTimerEventDelegate
        MyCheckInterval = iCheckInterval
        MyTimeOutValue = iTimeOutValue
        Dim ServerTimerDelegate As New TimerCallback(AddressOf ServerChangeListBox)
        MyServerTimer = New Timer(ServerTimerDelegate, Nothing, MyCheckInterval, MyTimeOutValue)

        autoEvents = New AutoResetEvent(3) { _
            New AutoResetEvent(False), _
            New AutoResetEvent(False), _
            New AutoResetEvent(False), _
            New AutoResetEvent(False)}

        manualEvent = New ManualResetEvent(False)
    End Sub

    Private Sub ServerTimerEvent(ByVal StatusMessage As String, ByVal ProcessMessage As String)
        If Not MyOnServerTimerEventDelegate Is Nothing Then
            MyOnServerTimerEventDelegate.Invoke(StatusMessage, ProcessMessage)
        End If
    End Sub

    Private Sub ManufacturingToProcessor(ByVal stateInfo As Object)
        Dim ds As DataSet
        Dim Result As Boolean
        Dim MySQLStr As String = "SELECT [Number],[ID],[PlanID],[PrepareTime],[Station],[MouldID]," _
                               & "      [MouldName],[Cart],[Code],[OutPut],[Outputtime],[FullStatus]" _
                               & " FROM  [Manufacturing] WHERE [MarkingToProcessor] IS NULL"
        Try
            MyServerTimer.Change(Timeout.Infinite, Timeout.Infinite)

            ds = MyServerCnn.ExecuteProcedureSQLSVR(MySQLStr)
            If ds.Tables(0).Rows.Count = 0 Then Exit Sub
            For i As Integer = 0 To ds.Tables(0).Rows.Count - 1
                MySQLStr = "INSERT INTO  [Processor]([Number],[ID],[PlanID],[PrepareTime],[Station]," _
                           & "      [MouldID],[MouldName],[Cart],[Code],[OutPut],[Outputtime],[Marking],[FullStatus])" _
                           & " VALUES ('" & ds.Tables(0).Rows(i)(0) & "','" & ds.Tables(0).Rows(i)(1) & "'," _
                           & " '" & ds.Tables(0).Rows(i)(2) & "','" & ds.Tables(0).Rows(i)(3) & "'," _
                           & " '" & ds.Tables(0).Rows(i)(4) & "','" & ds.Tables(0).Rows(i)(5) & "'," _
                           & " '" & ds.Tables(0).Rows(i)(6) & "','" & ds.Tables(0).Rows(i)(7) & "'," _
                           & " '" & ds.Tables(0).Rows(i)(8) & "'," & ds.Tables(0).Rows(i)(9) & "," _
                           & " convert(datetime,'" & ds.Tables(0).Rows(i)(10) & "',103),'1'" _
                           & ",'" & ds.Tables(0).Rows(i)(11) & "')"


                Result = MyServerCnn.ExecuteSQLSVR(MySQLStr)
                If Result = False Then
                    MyStatusString = "CHƯA CHUYỂN ĐƯỢC DỮ LIỆU MỚI TẠO HÌNH LÊN SERVER"
                Else
                    MyStatusString = "ĐÃ CHUYỂN DỮ LIỆU MỚI TẠO HÌNH LÊN SERVER"
                    MyProcessString = "CHUYỂN " & ds.Tables(0).Rows(i)(9) & " SP - MỚI TẠO HÌNH" & "+" & "ĐƠN HÀNG " _
                                    & ds.Tables(0).Rows(i)(1) & " LÊN SERVER"
                    MySQLStr = "Update  [Manufacturing]" _
                           & " Set [MarkingToProcessor] = '1'" _
                           & " Where [ID] = '" & ds.Tables(0).Rows(i)(1) & "'"
                    MyServerCnn.ExecuteSQLSVR(MySQLStr)
                End If
                ServerTimerEvent("", MyProcessString)
                MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
            Next
            ServerTimerEvent(MyStatusString, "")
            MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
            manualEvent.Set()
        Catch ex As Exception
            'MessageBox.Show(ex.Message)
        Finally
            MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
        End Try
    End Sub

    Private Sub TOCToProcessor(ByVal stateInfo As Object)
        Dim ds As DataSet
        Dim Result As Boolean
        Dim MySQLStr As String = "SELECT [ID],[PlanID],[Cart],[Output],[OutputControlTime],[Code]" _
                                & " FROM  [TOCDatabase] WHERE [MarkingToProcessor] IS NULL"
        Try
            MyServerTimer.Change(Timeout.Infinite, Timeout.Infinite)

            ds = MyServerCnn.ExecuteProcedureSQLSVR(MySQLStr)
            If ds.Tables(0).Rows.Count = 0 Then Exit Sub
            For i As Integer = 0 To ds.Tables(0).Rows.Count - 1
                MySQLStr = "Update [Processor]" _
                        & " Set    [OutPut] = " & ds.Tables(0).Rows(i)(3) & ", [Outputtime] = convert(datetime,'" & ds.Tables(0).Rows(i)(4) & "',103)" _
                        & " , [Code]= '" & ds.Tables(0).Rows(i)(5) & "', [Marking] = '2' " _
                        & " Where  [ID]= '" & ds.Tables(0).Rows(i)(0) & "'"
                Result = MyServerCnn.ExecuteSQLSVR(MySQLStr)
                If Result = False Then
                    MyStatusString = "CHƯA CHUYỂN ĐƯỢC DỮ LIỆU CÔNG ĐOẠN KIỂM SỐ LƯỢNG LÊN SERVER"
                Else
                    MyStatusString = "ĐÃ CHUYỂN DỮ LIỆU CÔNG ĐOẠN KIỂM SỐ LƯỢNG LÊN SERVER"
                    MyProcessString = "ĐÃ CHUYỂN " & ds.Tables(0).Rows(i)(3) & " SP - KIỂM SỐ LƯỢNG" & "+" & "ĐƠN HÀNG " _
                                    & ds.Tables(0).Rows(i)(0) & " LÊN SERVER"
                    MySQLStr = "Update  [TOCDatabase]" _
                           & " Set [MarkingToProcessor] = '1'" _
                           & " Where [ID] = '" & ds.Tables(0).Rows(i)(0) & "'"
                    MyServerCnn.ExecuteSQLSVR(MySQLStr)
                End If
                ServerTimerEvent("", MyProcessString)
                MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
                manualEvent.Set()
            Next
            manualEvent.WaitOne()
            ServerTimerEvent(MyStatusString, "")
            MyServerTimer.Change(MyCheckInterval, MyCheckInterval)

            autoEvents(0).Set()
        Catch ex As Exception
            'MessageBox.Show(ex.Message)
        Finally
            MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
        End Try
    End Sub

    Private Sub TQCToProcessor(ByVal stateInfo As Object)
        Dim ds As DataSet
        Dim Result As Boolean
        Dim MySQLStr As String = "SELECT [ID],[PlanID],[Cart],[QCOutPutOK],[QCTime],[Code]" _
                                & " FROM  [TQCDatabase] WHERE [MarkingToProcessor] IS NULL"
        Try
            MyServerTimer.Change(Timeout.Infinite, Timeout.Infinite)

            ds = MyServerCnn.ExecuteProcedureSQLSVR(MySQLStr)
            If ds.Tables(0).Rows.Count = 0 Then Exit Sub
            For i As Integer = 0 To ds.Tables(0).Rows.Count - 1
                MySQLStr = "Update [Processor]" _
                        & " Set    [OutPut] = " & ds.Tables(0).Rows(i)(3) & ", [Outputtime] = convert(datetime,'" & ds.Tables(0).Rows(i)(4) & "',103)" _
                        & " ,[Code] = '" & ds.Tables(0).Rows(i)(5) & "', [Marking] = '3' " _
                        & " Where  [ID]= '" & ds.Tables(0).Rows(i)(0) & "'"
                Result = MyServerCnn.ExecuteSQLSVR(MySQLStr)
                If Result = False Then
                    MyStatusString = "CHƯA CHUYỂN ĐƯỢC DỮ LIỆU CÔNG ĐOẠN KIỂM CHẤT LƯỢNG LÊN SERVER"
                Else
                    MyStatusString = "ĐÃ CHUYỂN DỮ LIỆU CÔNG ĐOẠN KIỂM CHẤT LƯỢNG LÊN SERVER"
                    MyProcessString = "ĐÃ CHUYỂN " & ds.Tables(0).Rows(i)(3) & " SP - KIỂM CHẤT LƯỢNG" & "+" & "ĐƠN HÀNG " _
                                    & ds.Tables(0).Rows(i)(0) & " LÊN SERVER"
                    MySQLStr = "Update  [TQCDatabase]" _
                           & " Set [MarkingToProcessor] = '1'" _
                           & " Where [ID] = '" & ds.Tables(0).Rows(i)(0) & "'"
                    MyServerCnn.ExecuteSQLSVR(MySQLStr)
                End If
                ServerTimerEvent("", MyProcessString)
                MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
                manualEvent.Set()
            Next
            manualEvent.WaitOne()
            ServerTimerEvent(MyStatusString, "")
            MyServerTimer.Change(MyCheckInterval, MyCheckInterval)

            autoEvents(1).Set()
        Catch ex As Exception
            'MessageBox.Show(ex.Message)
        Finally
            MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
        End Try
    End Sub

    Private Sub TransferringToProcessor(ByVal stateInfo As Object)
        Dim ds As DataSet
        Dim Result As Boolean
        Dim MySQLStr As String = "SELECT [ID],[PlanID],[Cart],[Quanlity],[ReceivingTime],[ReceivingCode]" _
                                & " FROM  [TTransferring] WHERE [MarkingToProcessor] IS NULL"
        Try
            MyServerTimer.Change(Timeout.Infinite, Timeout.Infinite)

            ds = MyServerCnn.ExecuteProcedureSQLSVR(MySQLStr)
            If ds.Tables(0).Rows.Count = 0 Then Exit Sub
            For i As Integer = 0 To ds.Tables(0).Rows.Count - 1
                MySQLStr = "Update [Processor]" _
                        & " Set    [OutPut] = " & ds.Tables(0).Rows(i)(3) & ", [Outputtime] = convert(datetime,'" & ds.Tables(0).Rows(i)(4) & "',103)" _
                        & " ,[Code] = '" & ds.Tables(0).Rows(i)(5) & "', [Marking] = '4' " _
                        & " Where  [ID]= '" & ds.Tables(0).Rows(i)(0) & "'"
                Result = MyServerCnn.ExecuteSQLSVR(MySQLStr)
                If Result = False Then
                    MyStatusString = "CHƯA CHUYỂN ĐƯỢC DỮ LIỆU CÔNG ĐOẠN GIAO NHẬN LÊN SERVER"
                Else
                    MyStatusString = "ĐÃ CHUYỂN DỮ LIỆU CÔNG ĐOẠN GIAO NHẬN LÊN SERVER"
                    MyProcessString = "ĐÃ CHUYỂN " & ds.Tables(0).Rows(i)(3) & " SP - KIỂM GIAO NHẬN" & "+" & "ĐƠN HÀNG " _
                                    & ds.Tables(0).Rows(i)(0) & " LÊN SERVER"
                    MySQLStr = "Update  [TTransferring]" _
                           & " Set [MarkingToProcessor] = '1'" _
                           & " Where [ID] = '" & ds.Tables(0).Rows(i)(0) & "'"
                    MyServerCnn.ExecuteSQLSVR(MySQLStr)
                End If
                ServerTimerEvent("", MyProcessString)
                MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
                manualEvent.Set()
            Next
            manualEvent.WaitOne()
            ServerTimerEvent(MyStatusString, "")
            MyServerTimer.Change(MyCheckInterval, MyCheckInterval)

            autoEvents(2).Set()
        Catch ex As Exception
            'MessageBox.Show(ex.Message)
        Finally
            MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
        End Try
    End Sub

    Private Sub GatherCart(ByVal stateInfo As Object)
        Dim dsStatusGather2 As DataSet
        Dim dsStatusGather1 As DataSet
        Dim Result As Boolean
        Dim CartID As String = ""
        Dim FormTime As String = ""
        Dim MySQLStr As String = "SELECT  [ID],[PlanID],[PrepareTime],[Station],[MouldID],[MouldName]," _
                                & " [Cart], [Code], [OutPut], [Outputtime], [Marking],[GatherCart]" _
                                & " FROM [Processor] WHERE [StatusGather] = '2'" ' Xe bị dồn lên
        Try
            MyServerTimer.Change(Timeout.Infinite, Timeout.Infinite)

            dsStatusGather2 = MyServerCnn.ExecuteProcedureSQLSVR(MySQLStr)
            If dsStatusGather2.Tables(0).Rows.Count = 0 Then Exit Sub

            For i As Integer = 0 To dsStatusGather2.Tables(0).Rows.Count - 1
                ''
                MySQLStr = "SELECT  [ID],[PlanID],[PrepareTime],[Station],[MouldID],[MouldName]," _
                        & " [Cart], [Code], [OutPut], [Outputtime], [Marking],[GatherCart]" _
                        & " FROM [Processor] WHERE [StatusGather] = '1'" _
                        & " AND [GatherCart] = '" & dsStatusGather2.Tables(0).Rows(i)(11) & "'" ' Các xe được lấy ra để dồn
                dsStatusGather1 = MyServerCnn.ExecuteProcedureSQLSVR(MySQLStr)

                For j As Integer = 0 To dsStatusGather1.Tables(0).Rows.Count - 1
                    MySQLStr = "INSERT INTO  [GatherCartHistory]([ID],[PlanID],[PrepareTime],[Station]," _
                              & "      [MouldID],[MouldName],[Cart],[Code],[OutPut],[Outputtime],[Marking],[GatherTime])" _
                              & " VALUES ('" & dsStatusGather1.Tables(0).Rows(j)(0) & "','" & dsStatusGather1.Tables(0).Rows(j)(1) & "'," _
                              & " '" & dsStatusGather1.Tables(0).Rows(j)(2) & "','" & dsStatusGather1.Tables(0).Rows(j)(3) & "'," _
                              & " '" & dsStatusGather1.Tables(0).Rows(j)(4) & "','" & dsStatusGather1.Tables(0).Rows(j)(5) & "'," _
                              & " '" & dsStatusGather1.Tables(0).Rows(j)(6) & "','" & dsStatusGather1.Tables(0).Rows(j)(7) & "'," _
                              & dsStatusGather1.Tables(0).Rows(j)(8) & ", convert(datetime,'" & dsStatusGather1.Tables(0).Rows(j)(9) & "',103)" _
                              & " ,'" & dsStatusGather1.Tables(0).Rows(j)(10) & "',convert(datetime,'" & Now() & "',103))"
                    Result = MyServerCnn.ExecuteSQLSVR(MySQLStr)
                    If Result = False Then
                        MyStatusString = "CHƯA CHUYỂN ĐƯỢC DỮ LIỆU CÔNG ĐOẠN DỒN XE LÊN SERVER"
                    Else
                        MyStatusString = "ĐÃ CHUYỂN DỮ LIỆU CÔNG ĐOẠN DỒN XE LÊN SERVER"
                        MyProcessString = "ĐÃ CHUYỂN " & dsStatusGather1.Tables(0).Rows(j)(8) & " SP - KIỂM DỒN XE" & "+" & "ĐƠN HÀNG " _
                                        & dsStatusGather1.Tables(0).Rows(j)(0) & " TỪ XE " & dsStatusGather1.Tables(0).Rows(j)(6) _
                                        & " QUA XE " & dsStatusGather2.Tables(0).Rows(i)(11) & " LÊN SERVER"

                        'insert vao bang CartHistory nhung xe duoc lay ra de don
                        CartID = dsStatusGather2.Tables(0).Rows(i)(6) & Format(Now(), "ddMMyyHHmmss")
                        FormTime = MyServerCnn.GetFormTime(dsStatusGather1.Tables(0).Rows(j)(0))
                        MySQLStr = "INSERT INTO [CartHistory]([ID],[UsingCart],[OriginalCart],[SystemTime]) " _
                                & "  VALUES ('" & CartID & "','" & dsStatusGather1.Tables(0).Rows(j)(6) & "'," _
                                & " '" & dsStatusGather2.Tables(0).Rows(i)(6) & "',convert(datetime,'" & FormTime & "',103))"
                        MyServerCnn.ExecuteSQLSVR(MySQLStr)

                        'Update lai tinh trang xe trong trong bang TrollyList
                        MySQLStr = "UPDATE  [CartList] SET [Status] = '0'" _
                                & "  WHERE [Cart] = '" & dsStatusGather1.Tables(0).Rows(j)(6) & "'"
                        MyServerCnn.ExecuteSQLSVR(MySQLStr)

                        'Xoa thong tin xe cac xe nay trong bang Processor
                        MySQLStr = "DELETE  [Processor]" _
                               & "  WHERE [ID] = '" & dsStatusGather1.Tables(0).Rows(j)(0) & "'"
                        MyServerCnn.ExecuteSQLSVR(MySQLStr)
                    End If
                    ServerTimerEvent("", MyProcessString)
                    MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
                    manualEvent.Set()
                Next

                'update lai trang thai StatusGather = 3
                MySQLStr = "UPDATE  [Processor]" _
                        & " SET [StatusGather] = '3'" _
                        & " WHERE [ID] = '" & dsStatusGather2.Tables(0).Rows(i)(0) & "'"
                MyServerCnn.ExecuteSQLSVR(MySQLStr)

                'insert vao bang CartHistory xe bi don len
                CartID = dsStatusGather2.Tables(0).Rows(i)(6) & Format(Now(), "ddMMyyhhmmss")
                FormTime = MyServerCnn.GetFormTime(dsStatusGather2.Tables(0).Rows(i)(0))
                MySQLStr = "INSERT INTO [CartHistory]([ID],[UsingCart],[OriginalCart],[SystemTime]) " _
                        & "  VALUES ('" & CartID & "','" & dsStatusGather2.Tables(0).Rows(i)(6) & "'," _
                        & " '" & dsStatusGather2.Tables(0).Rows(i)(6) & "',convert(datetime,'" & FormTime & "',103))"
                MyServerCnn.ExecuteSQLSVR(MySQLStr)
                ''
            Next
            manualEvent.WaitOne()
            ServerTimerEvent(MyStatusString, "")
            MyServerTimer.Change(MyCheckInterval, MyCheckInterval)

            autoEvents(2).Set()
        Catch ex As Exception
            'MessageBox.Show(ex.Message)
        Finally
            MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
        End Try
    End Sub

    Private Sub ServerChangeListBox(ByVal stateInfo As Object)

        MyServerTimer.Change(Timeout.Infinite, Timeout.Infinite)

        Try
            ThreadPool.QueueUserWorkItem(AddressOf ManufacturingToProcessor)
            ThreadPool.QueueUserWorkItem(AddressOf TOCToProcessor)
            ThreadPool.QueueUserWorkItem(AddressOf TQCToProcessor)
            ThreadPool.QueueUserWorkItem(AddressOf TransferringToProcessor)
            ThreadPool.QueueUserWorkItem(AddressOf GatherCart)

            WaitHandle.WaitAll(autoEvents)

            ' Reset the wait handle for the next calculation.
            manualEvent.Reset()
        Catch ex As Exception

        Finally
            MyServerTimer.Change(MyCheckInterval, MyCheckInterval)
        End Try

        ' ''MyServerTimer.Change(Timeout.Infinite, Timeout.Infinite)
        ' ''ServerTimerEvent("CHANGE")
        ' ''MyServerTimer.Change(MyCheckInterval, MyCheckInterval)

    End Sub

    Public Overridable Sub Dispose()
        SyncLock Me
            Me.MyServerTimer.Dispose()
        End SyncLock
    End Sub

End Class
